#include "TelephoneBook.h"
#include "TelephoneInfo.h"

#include <stdio.h>
#include <stdbool.h>
#include <string.h>
#include <stdlib.h>

struct TelephoneBook
{
    ElementType *array; // 数组指针
    int capacity;       // 数组容量
    int size;           // 数组大小
};

//初始化
Telebook *InitTelebook()
{
    Telebook *t = (Telebook *)malloc(sizeof(Telebook));
    if (t == NULL)
    {
        printf("InitTelebook malloc error!\n");
        exit(-1);
    }
    t->size = 0;
    t->capacity = 10;
    t->array = (ElementType *)malloc(sizeof(ElementType) * t->capacity);
    if (t->array == NULL)
    {
        printf("InitTelebook array error!\n");
        exit(-1);
    }
    return t; 
}
//插入
void  insert_Telebook(Telebook *t,int flag)
{
       if (t->size == t->capacity)
    {
        t->capacity *= 2; // 可以扩两倍
        t->array = (ElementType *)realloc(t->array, t->capacity * sizeof(ElementType));
        if (t->array == NULL)
        {
            printf("InitTelebook realloc error!\n");
            exit(-1);
        }
    }
    if(flag==1)
    t->array[t->size++] = CreateTelInfo();
    if(flag==2)
    {
         FILE *f=fopen("./telephone.txt","r");
    if(!f){
        printf("文件读取失败\n");
        return;
    }
        t->array[t->size++] = CreateFIleTelInfo(f);
    }
}
void insert_sort(Telebook *t,bool (*compare)(elementType,elementType))
{
    for(int i=1;i<t->size;i++){
        int j=i;
        //这个位置是即将要插入的数
       ElementType temp=t->array[i];
        for(;j>0;j--)
        {
            if(compare(t->array[j-1],temp)){
                t->array[j]=t->array[j-1];
            }
            else{//前面的数不比我大
                break;//此时a[j]为上一次循环的a[j-1]
            }
        }
        
        t->array[j]=temp;//序号j-1的数<=temp,现在的j是上次的j-1被挪了，可插入
    }
}

//删除
ElementType RemoveByIndex(Telebook *t, int index)
{
     ElementType result = t->array[index];
    for (int i = index; i < t->size - 1; i++)
    {
        t->array[i] = t->array[i + 1];
    }
    t->size--;
    return result;
}
ElementType delete_Telebook(Telebook *t, bool (*compare)(ElementType, ElementType))
{
    printf("请输入要移除的用户名字/电话号码: \n");
    getchar();
    char value[15];
    scanf("%s", value);
    for (int i = 0; i < t->size; i++)
    {
        if (compare(t->array[i], value))
        {
           return RemoveByIndex(t, i);
        }
    }
    return NULL;
}
//查看
ElementType BinarySearch(Telebook *t,ElementType value,int(*compare)(ElementType, ElementType))
{
    int left=0;
    int right=t->size-1;
    while(left<=right)
    {
        //取中间值
        int mid=left+(right-left)/2;
        //(left&right)+((left^right)>>1);left+(right-left)/2;
        if(compare(t->array[mid],value)==0)
        {
            return t->array[mid];
        }
        else if(compare(t->array[mid],value)>0)
        {
            right=mid-1;
        }
        else if(compare(t->array[mid],value)<0)
        {
            left=mid+1;
        }
    }
        return NULL;

}
//修改
void modify_Telebook(Telebook *t, bool (*compare)(ElementType, ElementType))
{
    printf("请输入要修改的用户名字/电话号码: \n");
    char value[15];
    scanf("%s", value);
    for (int i = 0; i < t->size; i++)
    {
        if (compare(t->array[i], value))
        {
            ClearTeleInfo(t->array[i]);
            t->array[i] =CreateTelInfo();
        }
    }
}
//展示
void display_Telebook(Telebook *t, void (*print)(ElementType))
{
     printf("联系人信息: \n");
    for (int i = 0; i < t->size; i++)
    {
        print(t->array[i]);
    }
    printf("\n");
    getchar();
}
void display_Telebook2(Telebook *t, void (*print)(ElementType))
{
     printf("联系人信息: \n");
    for (int i = t->size-1; i >=0; i--)
    {
        print(t->array[i]);
    }
    printf("\n");
    getchar();
  
}
//清除内存
void Clear_Telebook(Telebook *t, void (*clear)(ElementType))
{
     if (t != NULL)
    {
        for (int i = 0; i < t->size; i++)
        {
            clear(t->array[i]);
        }
        free(t->array);
        free(t);
}
}
void Save_Telbook(Telebook *t,void(*save)(ElementType,FILE*))
{
    FILE *f=fopen("./telephone.txt","w");
    if(!f){
        printf("文件写入失败\n");
        return;
    }
    for(int i=0;i<a->size;i++){
        save(t->array[i],f);//函数指针 指向代码段
    }

}